﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespace ClientLib.Common
{
    public enum DataType { NULL, INT, DOUBLE, STRING, BOOL, INT_ARRAY, DOUBLE_ARRAY, STRING_ARRAY, BOOL_ARRAY }

    public struct DeviceSign { public string dev_id; public string mon_id;}

    public struct ChangeStateBackInfo { public bool isSucess; public string info;}
    
    public class AttributeValue:IComparable<AttributeValue>
    {
        DataType dataType;
        object value;

        /*********************************************
        构造函数1
        *********************************************/
        public AttributeValue()
        {
            dataType = DataType.NULL;//初始化为空类型
        }

        /*********************************************
        构造函数2
        *********************************************/
        public AttributeValue(DataType type, object value)
        {
            setDataValue(type, value);
        }

        public AttributeValue(string strtype,Object value)
        {
            DataType type = mapType(strtype);
            setDataValue(type, value);
        }


        /*********************************************
        获取数据类型
        *********************************************/
        public DataType getDataType()
        {
            return dataType;
        }

        /*********************************************
        获取数据值
        *********************************************/
        public object getDataValue()
        {
            return value;
        }

        /*********************************************
        设置数据
        *********************************************/
        public void setDataValue(object value)
        {
            try
            {
                switch (this.dataType)
                {
                    //-------值类型属性-------
                    case DataType.BOOL:
                        this.value = Convert.ToBoolean(value);
                        break;
                    case DataType.DOUBLE:
                        this.value = Convert.ToDouble(value);
                        break;
                    case DataType.INT:
                        this.value = Convert.ToInt32(value);
                        break;
                    case DataType.STRING:
                        this.value = Convert.ToString(value);
                        break;
                    //------引用类型属性-------
                    case DataType.INT_ARRAY:
                        if (value.GetType().Name.Equals("Int32[]"))
                            this.value = value;
                        else
                            throw new Exception("invalid argument: type--INT_ARRAY");
                        break;
                    case DataType.DOUBLE_ARRAY:
                        if (value.GetType().Name.Equals("Double[]"))
                            this.value = value;
                        else
                            throw new Exception("invalid argument: type--DOUBLE_ARRAY");
                        break;
                    case DataType.STRING_ARRAY:
                        if (value.GetType().Name.Equals("String[]"))
                            this.value = value;
                        else
                            throw new Exception("invalid argument: type--STRING_ARRAY");
                        break;
                    case DataType.BOOL_ARRAY:
                        if (value.GetType().Name.Equals("Boolean[]"))
                            this.value = value;
                        else
                            throw new Exception("invalid argument: type--BOOL_ARRAY");
                        break;
                    //-------类型异常-------
                    default:
                        throw new Exception("invalid argument: type");
                }
            }
            catch (Exception e)
            {
                throw e;
            }
        }

        /*********************************************
        设置类型和数据
        *********************************************/
        public void setDataValue(DataType type, object value)
        {
            this.dataType = type;

            try
            {
                switch (type)
                {
                    //-------值类型属性-------
                    case DataType.BOOL:
                        this.value = Convert.ToBoolean(value);
                        break;
                    case DataType.DOUBLE:
                        this.value = Convert.ToDouble(value);
                        break;
                    case DataType.INT:
                        this.value = Convert.ToInt32(value);
                        break;
                    case DataType.STRING:
                        this.value = Convert.ToString(value);
                        break;
                    //------引用类型属性-------
                    case DataType.INT_ARRAY:
                        if (value.GetType().Name.Equals("Int32[]"))
                            this.value = value;
                        else
                            throw new Exception("invalid argument: type--INT_ARRAY");
                        break;
                    case DataType.DOUBLE_ARRAY:
                        if (value.GetType().Name.Equals("Double[]"))
                            this.value = value;
                        else
                            throw new Exception("invalid argument: type--DOUBLE_ARRAY");
                        break;
                    case DataType.STRING_ARRAY:
                        if (value.GetType().Name.Equals("String[]"))
                            this.value = value;
                        else
                            throw new Exception("invalid argument: type--STRING_ARRAY");
                        break;
                    case DataType.BOOL_ARRAY:
                        if (value.GetType().Name.Equals("Boolean[]"))
                            this.value = value;
                        else
                            throw new Exception("invalid argument: type--BOOL_ARRAY");
                        break;
                    //-------类型异常-------
                    default:
                        throw new Exception("invalid argument: type");
                }
            }
            catch (Exception e)
            {
                throw e;
            }
        }

        /*********************************************
        返回值的字符串
        *********************************************/
        public override string ToString()
        {
            switch (this.dataType)
            {
                case DataType.BOOL:
                    return this.value.ToString().ToLower();
                case DataType.DOUBLE:
                    return this.value.ToString();
                case DataType.INT:
                    return this.value.ToString();
                case DataType.STRING:
                    return this.value.ToString();
                default:
                    throw new ApplicationException("");
            }
        }
       
        /*********************************************
        将字符串标示的类型映射到DataType类型上
        *********************************************/
        public static DataType mapType(string strType)
        {
            if (strType == null)
                throw (new NullReferenceException("参数对象为Null"));
            if (strType.ToLower() == "double")
            {
                return DataType.DOUBLE;
            }
            else if (strType.ToLower() == "int")
            {
                return DataType.INT;
            }
            else if (strType.ToLower() == "bool")
            {
                return DataType.BOOL;
            }
            else if (strType.ToLower() == "string")
            {
                return DataType.STRING;
            }
            else
            {
                throw (new ApplicationException("字符串标示的类型映射到DataType类型出错：不存在此类型" + strType));
            }
        }

        /*********************************************
        指定一个类型，针对该类型初始化一个值对象
        *********************************************/
        public void initValByType(string strType)
        {
            try
            {
                this.dataType = mapType(strType);
                switch (this.dataType)
                {
                    case DataType.INT:
                        this.value = 0;
                        break;
                    case DataType.DOUBLE:
                        this.value = 0;
                        break;
                    case DataType.BOOL:
                        this.value = 0;
                        break;
                    default:
                        throw (new ApplicationException(strType + "类型无法进行值的初始化"));
                }
            }
            catch (Exception e)
            {
                //Console.WriteLine(e.StackTrace + ":" + e.Message);
                throw (new ApplicationException(e.Message));
            }

        }
        /*********************************************
       实现ICompare接口
       *********************************************/
        public bool Equals(AttributeValue other)
        {
            if (this.dataType != other.dataType)
            {
                return false;
            }
            else
            {
            

                try
                {
                    switch (this.dataType)
                    {
                        //-------值类型属性-------
                        case DataType.BOOL:
                            return (bool)this.value == (bool)other.value;
                           
                        case DataType.DOUBLE:
                            return (double)this.value == (double)other.value;

                        case DataType.INT:
                            return (int)this.value == (int)other.value;

                        case DataType.STRING:
                            return (string)this.value == (string)other.value;

                        ////------引用类型属性-------
                        ////case DataType.INT_ARRAY:
                        ////    if (value.GetType().Name.Equals("Int32[]"))
                        ////        this.value = value;
                        ////    else
                        ////        throw new Exception("invalid argument: type--INT_ARRAY");
                        ////    break;
                        //case DataType.DOUBLE_ARRAY:
                        //    if (value.GetType().Name.Equals("Double[]"))
                        //        this.value = value;
                        //    else
                        //        throw new Exception("invalid argument: type--DOUBLE_ARRAY");
                        //    break;
                        //case DataType.STRING_ARRAY:
                        //    if (value.GetType().Name.Equals("String[]"))
                        //        this.value = value;
                        //    else
                        //        throw new Exception("invalid argument: type--STRING_ARRAY");
                        //    break;
                        //case DataType.BOOL_ARRAY:
                        //    if (value.GetType().Name.Equals("Boolean[]"))
                        //        this.value = value;
                        //    else
                        //        throw new Exception("invalid argument: type--BOOL_ARRAY");
                        //    break;
                        //-------类型异常-------
                        default:
                            return false;
                    }
                }
                catch (Exception e)
                {
                    throw e;
                }
            }
        }

        public int CompareTo(AttributeValue other)
        {
            if (this.dataType != other.dataType)
            {
                return -1;
            }
            else
            {


                try
                {
                    switch (this.dataType)
                    {
                        //-------值类型属性-------
                        case DataType.BOOL:
                            return ((bool)this.value).CompareTo((bool)other.value);

                        case DataType.DOUBLE:
                            return ((double)this.value).CompareTo((double)other.value);

                        case DataType.INT:
                            return ((int)this.value).CompareTo((int)other.value);

                        case DataType.STRING:
                            return ((string)this.value).CompareTo((string)other.value);
                        ////------引用类型属性-------
                        ////case DataType.INT_ARRAY:
                        ////    if (value.GetType().Name.Equals("Int32[]"))
                        ////        this.value = value;
                        ////    else
                        ////        throw new Exception("invalid argument: type--INT_ARRAY");
                        ////    break;
                        //case DataType.DOUBLE_ARRAY:
                        //    if (value.GetType().Name.Equals("Double[]"))
                        //        this.value = value;
                        //    else
                        //        throw new Exception("invalid argument: type--DOUBLE_ARRAY");
                        //    break;
                        //case DataType.STRING_ARRAY:
                        //    if (value.GetType().Name.Equals("String[]"))
                        //        this.value = value;
                        //    else
                        //        throw new Exception("invalid argument: type--STRING_ARRAY");
                        //    break;
                        //case DataType.BOOL_ARRAY:
                        //    if (value.GetType().Name.Equals("Boolean[]"))
                        //        this.value = value;
                        //    else
                        //        throw new Exception("invalid argument: type--BOOL_ARRAY");
                        //    break;
                        //-------类型异常-------
                        default:
                            return -1;
                    }
                }
                catch (Exception e)
                {
                    throw e;
                }
            }
        }
    }
}
